#include "StdAfx.h"



CGameManager::CGameManager(HWND hWnd, HINSTANCE hInstance)
{
	this->_hWnd = hWnd;
	this->_hInstance = hInstance;
}

CGameManager::~CGameManager(void)
{

}

void CGameManager::Initialize()
{
	
	_graphics.CreateDoubleBuffering(_hWnd);
	_tile.SetHBitmap(_graphics.LoadBitmapFromResource(IDB_BITMAP2, this->_hInstance));
	_tile.SetDirection(DIRECTION_RIGHT);
	_tile.SetLocation(0, 0);
	_tile.GetSections()->clear();
	_lastRender = 0.0f;
	_scoreBoard.Initialize(&_graphics, _hInstance);
	_foodApple.SetHBitmap(_graphics.LoadBitmapFromResource(IDB_APPLE, this->_hInstance));
	_foodOrange.SetHBitmap(_graphics.LoadBitmapFromResource(IDB_ORANGE, this->_hInstance));
	_foodBanana.SetHBitmap(_graphics.LoadBitmapFromResource(IDB_BANANA, this->_hInstance));
	_foodCherries.SetHBitmap(_graphics.LoadBitmapFromResource(IDB_CHERRIES, this->_hInstance));
	_foodGrapes.SetHBitmap(_graphics.LoadBitmapFromResource(IDB_GRAPES, this->_hInstance));
	RECT r = _scoreBoard.GetCurrentGameWindow(this->_hWnd);
	PlantSomeFood(&r);
	this->_bDrawMenu = true;
	_menu.Initialize(&_graphics, _hInstance);
	_menu.AddMenuItem(L"Easy");
	_menu.AddMenuItem(L"Medium");
	_menu.AddMenuItem(L"Hard");
}

WPARAM CGameManager::RunGame()
{
	MSG msg;			// a window message

	while(1)
	{
		if(PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
		{
			if(msg.message == WM_QUIT)
			{
				break;		// user wants to quit
			}
			if(msg.message == WM_KEYDOWN)
			{
				if(_bDrawMenu)
				{
					_menu.HandleKeyStroke(msg.wParam);
				}
				else
				{
					_tile.SetDirection(msg.wParam);
				}
			}

		}

			TranslateMessage(&msg);
			DispatchMessage(&msg);
			
			
			if(this->_bDrawMenu)
			{
				RECT rect;
				GetClientRect(this->_hWnd, &rect);
				_menu.Draw(&rect, &_graphics);
				if(_menu.DifficultySelected() == true)
				{
					_bDrawMenu = false;
					this->_nDifficulty = 5 * (1 + _menu.GetIndex());
					GetClientRect(this->_hWnd, &rect);
					_graphics.ClearPortionOfScreen(BLACK_BRUSH, rect);
				}
				_graphics.FlipBuffers(false);
				Sleep(30);

			}

			// do rendering, moving, etc.. here
			else if(this->AnimateNextFrame(_nDifficulty))
			{
				Erase();
				EraseBack();
				RECT rect;
				GetClientRect(this->_hWnd, &rect);
				RECT playableRect = _scoreBoard.GetCurrentGameWindow(this->_hWnd);
				_tile.Move(&playableRect);
				RECT snakeRect;
				snakeRect.left = _tile.GetLocation().x;
				snakeRect.right = snakeRect.left + SEGMENT_WIDTH;
				snakeRect.top = _tile.GetLocation().y;
				snakeRect.bottom = snakeRect.top + SEGMENT_HEIGHT;

				if((int)_tile.GetSections()->size() > 0)
				{
				
					for( int i = 0; i < (int)_tile.GetSections()->size(); i++)
					{
						if(AreTheSame(&snakeRect, &_tile.GetSections()->at(i)))
						{
							MessageBox(this->_hWnd, L"You died!", L"Game Over!", MB_OK);
							Initialize();
							break;
						}
						
					}


				}

				if(CheckForFood())
				{
					// erase the food
					EraseFood();
					_scoreBoard.SetScore(_scoreBoard.GetScore() + 8);
					RECT playable = _scoreBoard.GetCurrentGameWindow(this->_hWnd);
					PlantSomeFood(&playable);
					_tile.AddSection();
				}
				RenderScene();
				GetClientRect(this->_hWnd, &rect);
				_scoreBoard.DrawScoreBoard(&_graphics, &rect);
			}

	}


	return msg.wParam;


}

bool CGameManager::CheckForFood()
{
	// check to see if the head is intersecting with the fruit
	RECT foodBoundary;
	foodBoundary.left = this->_ptFoodLocation.x;
	foodBoundary.right = foodBoundary.left + SEGMENT_WIDTH;
	foodBoundary.top = this->_ptFoodLocation.y;
	foodBoundary.bottom = foodBoundary.top + SEGMENT_HEIGHT;

	RECT headBoundary;
	headBoundary.left = this->_tile.GetLocation().x;
	headBoundary.right = headBoundary.left + SEGMENT_WIDTH;
	headBoundary.top = this->_tile.GetLocation().y;
	headBoundary.bottom = headBoundary.top + SEGMENT_HEIGHT;

	if((((headBoundary.right >= foodBoundary.left) && (headBoundary.left <= foodBoundary.right))&& ((headBoundary.bottom >= foodBoundary.top) && (headBoundary.top <= foodBoundary.bottom))) ||
	(((headBoundary.left <= foodBoundary.right) && (headBoundary.right >= foodBoundary.left)) && ((headBoundary.top <= foodBoundary.bottom) && headBoundary.bottom >= foodBoundary.top)))
	{
		return true;
	}
	else
	{
		return false;
	}

}

//Check to see if two rectangles have the same coordinates
bool CGameManager::AreTheSame(RECT *pRect1, RECT *pRect2)
{
	if((pRect1->bottom == pRect2->bottom) &&
		(pRect1->left == pRect2->left) &&
		(pRect1->right == pRect2->right) &&
		(pRect1->top == pRect2->top))
	{
		return true;
	}
	else
	{
		return false;
	}
}


void CGameManager::EraseFood()
{
				RECT portion;
				portion.left = _ptFoodLocation.x;
				portion.right = portion.left + SEGMENT_WIDTH;
				portion.top = _ptFoodLocation.y;
				portion.bottom = portion.top + SEGMENT_HEIGHT;
				_graphics.ClearPortionOfScreen(BLACK_BRUSH, portion);

}
void CGameManager::Erase()
{
				RECT portion;
				portion.left = _tile.GetLocation().x;
				portion.right = portion.left + SEGMENT_WIDTH;
				portion.top = _tile.GetLocation().y;
				portion.bottom = portion.top + SEGMENT_HEIGHT;
				_graphics.ClearPortionOfScreen(BLACK_BRUSH, portion);

}

void CGameManager::EraseBack()
{
	if(_tile.GetSections()->size() > 0)
	{
	RECT portion;
				portion.left = _tile.GetSections()->back().left;
				portion.right = _tile.GetSections()->back().left + SEGMENT_WIDTH;
				portion.top = _tile.GetSections()->back().top;
				portion.bottom = _tile.GetSections()->back().top + SEGMENT_HEIGHT;
				_graphics.ClearPortionOfScreen(BLACK_BRUSH, portion);
	}
}




void CGameManager::RenderScene()
{
	// draw the snake head
	_graphics.DisplayBitmap(_tile.GetHBitmap(), _tile.GetLocation().x, _tile.GetLocation().y);
	// draw the snake sections
	for(int i = 0; i < (int)_tile.GetSections()->size(); i++)
	{
		_graphics.DisplayBitmap(_tile.GetHBitmap(), _tile.GetSections()->at(i).left, _tile.GetSections()->at(i).top);
	}
	// draw the food
	_graphics.DisplayBitmap(_hbmpFood, _ptFoodLocation.x, _ptFoodLocation.y);

	_graphics.FlipBuffers(false);

}

bool CGameManager::AnimateNextFrame(int desiredFrameRate)
{
	float currentTime = GetTickCount() * 0.001f;
	float elapsedTime = currentTime - _lastRender;
	if(elapsedTime > (1.0f / desiredFrameRate))
	{
		_lastRender = currentTime;

		return true;
	}
	else
		return false;

}

void CGameManager::PlantSomeFood(RECT *pPlayableRect)
{
	srand(GetTickCount());						// seed the random algorithm with a time variable
	int randomd = rand() % 5 + 1;			// generate a random number between 1 and 5;
	_ptFoodLocation.x = rand() % (pPlayableRect->right - SEGMENT_WIDTH);
	_ptFoodLocation.y = rand() % (pPlayableRect->bottom - SEGMENT_HEIGHT);

	switch(randomd)
	{
	case 1:
		_hbmpFood = _foodApple.GetHBitmap();
		break;

	case 2:
		_hbmpFood = _foodOrange.GetHBitmap();
		break;

	case 3:
		_hbmpFood = _foodBanana.GetHBitmap();
		break;

	case 4:
		_hbmpFood = _foodCherries.GetHBitmap();
		break;

	case 5:
		_hbmpFood = _foodGrapes.GetHBitmap();
		break;
	default:
		break;
		
	}

	return;

}